/*
创建人：Liujm(cdtye)
创建日期：2019年11月5日
功能描述：几何要素编辑组件
使用说明：
输入： props 中的
    geometryJson 现有的geometry json 对象，可选参数
    geometryType geometry的类型，当geometryJson为空时，必须输入 有效值  point|polyline|polygon (注意大小写敏感)
    readOnly  是否只读  默认为false
输出：
    请通过方法
    geometrycallback({geometry:{},geojson:{}})  接收编辑后返回的结果
 */
<template>
  <div class="geometry-editor" :style="{width: width, height: height}">
    <app-mapview basemap="IMG" @mapview-loaded="mapviewLoaded" />
    <base-dialog
      class="editor-dialog"
      fullscreen
      append-to-body
      confirm-text="确认"
      :visible.sync="pointDialog.visible"
      :title="title"
      :loading="pointDialog.loading"
      :disabled="pointDialog.disabled"
      :show-default-footer="!readOnly"
      @updateData="updateData">
      <point-editor ref="point" :geometry="geometry" :symbol="markSymbol" :read-only="readOnly" />
    </base-dialog>
    <base-dialog
      class="editor-dialog"
      fullscreen
      append-to-body
      confirm-text="确认"
      :visible.sync="polylineDialog.visible"
      :title="title"
      :loading="polylineDialog.loading"
      :disabled="polylineDialog.disabled"
      :show-default-footer="!readOnly"
      @updateData="updateData">
      <polyline-editor ref="polyline" :geometry="geometry" :symbol="lineSymbol" :read-only="readOnly" />
    </base-dialog>
    <base-dialog
      class="editor-dialog"
      fullscreen
      append-to-body
      confirm-text="确认"
      :visible.sync="polygonDialog.visible"
      :title="title"
      :loading="polygonDialog.loading"
      :disabled="polygonDialog.disabled"
      :show-default-footer="!readOnly"
      @updateData="updateData">
      <polygon-editor ref="polygon" :geometry="geometry" :symbol="fillSymbol" :read-only="readOnly" />
    </base-dialog>
  </div>
</template>
<script>
import { loadModules } from 'esri-loader'
import appMapview from '@/components/ItpsMap/AppMapview'
import { geometryToGeojson, geometryToJson, addRaiwayLayers } from '@/utils/gis.js'
import { getMapService } from '@/api/dsc/gis/basic'
import PointEditor from '@/components/ItpsMap/GeometryEditor/point'
import PolylineEditor from '@/components/ItpsMap/GeometryEditor/polyline'
import PolygonEditor from '@/components/ItpsMap/GeometryEditor/polygon'

export default {
  components: {
    appMapview, PointEditor, PolylineEditor, PolygonEditor
  },
  props: {
    geometryJson: {
      // 可选的传入参数，对应 geometry 的json对象
      type: Object
    },
    geometryType: {
      // 当geometryJson不为空的时候可以不传
      // 当geometryJson参数没有时为必须参数 有效值为 point|polyline|polygon (注意大小写敏感)
      type: String
    },
    readOnly: {
      type: Boolean,
      default: false
    },
    width: {
      type: String,
      default: '300px'
    },
    height: {
      type: String,
      default: '200px'
    },
    title: {
      type: String,
      default: '编辑要素'
    }
  },
  data() {
    return {
      geometry: null,
      pointDialog: {
        visible: false,
        loading: false,
        disabled: false,
        form: {
          data: []
        }
      },
      polylineDialog: {
        visible: false,
        loading: false,
        disabled: false,
        form: {
          data: []
        }
      },
      polygonDialog: {
        visible: false,
        loading: false,
        disabled: false,
        form: {
          data: []
        }
      },
      view: null,
      graphicsLyr: null,
      webMercatorUtils: null,
      markSymbol: {
        type: 'simple-marker', // autocasts as new SimpleMarkerSymbol()
        style: 'square',
        color: 'red',
        size: '8px', // pixels
        outline: { // autocasts as new SimpleLineSymbol()
          color: [255, 255, 0],
          width: 3 // points
        }
      },
      lineSymbol: {
        type: 'simple-line',
        color: [1, 153, 1],
        width: '6px',
        join: 'round'
      },
      fillSymbol: {
        type: 'simple-fill', // autocasts as new SimpleFillSymbol()
        color: [51, 51, 204, 0.9],
        style: 'solid',
        outline: { // autocasts as new SimpleLineSymbol()
          color: 'white',
          width: 1
        }
      }
    }
  },
  watch: {
    geometryJson(oldV, newV) {
      // eslint-disable-next-line no-undef
      loadModules(['esri/Graphic', 'esri/geometry/Point', 'esri/geometry/Polyline', 'esri/geometry/Polygon'], { url: window.MAP_CONFIG().jsapi }).then(([Graphic, Point, Polyline, Polygon]) => {
        this.graphicsLyr.graphics.removeAll()
        this.initGraphic(Point, Polyline, Polygon, Graphic)
      })
    }
  },
  mounted() { },
  methods: {
    mapviewLoaded(paramters) {
      this.view = paramters.view
      loadModules(['esri/Graphic', 'esri/geometry/Point', 'esri/geometry/Polyline', 'esri/geometry/Polygon',
        'esri/layers/BaseTileLayer',
        'esri/layers/WMTSLayer',
        'esri/layers/MapImageLayer', 'esri/layers/GraphicsLayer',
        'esri/geometry/support/webMercatorUtils'
      // eslint-disable-next-line no-undef
      ], { url: window.MAP_CONFIG().jsapi })
        .then(([
          Graphic, Point, Polyline, Polygon,
          BaseTileLayer, WMTSLayer, MapImageLayer, GraphicsLayer, webMercatorUtils
        ]) => {
          this.webMercatorUtils = webMercatorUtils

          // 添加铁路线路
          getMapService({ serviceCodes: 'BZGTL,CZ,CZZJ' }).then(res => {
            // 添加铁路线路图层
            if (res.data && res.data.length > 0) {
              addRaiwayLayers(this.view.map, BaseTileLayer, WMTSLayer, MapImageLayer, res.data)
            }
          })

          this.graphicsLyr = new GraphicsLayer({ title: '几何编辑' })

          this.view.map.add(this.graphicsLyr)
          this.view.on('double-click', (evt) => {
            evt.stopPropagation()
            let editor = null
            switch (this.geometryType) {
              case 'point':
                this.pointDialog.visible = true
                editor = this.$refs.point
                break
              case 'polyline':
                this.polylineDialog.visible = true
                editor = this.$refs.polyline
                break
              case 'polygon':
                this.polygonDialog.visible = true
                editor = this.$refs.polygon
                break
              default:
                console.log('不支持的Geomety')
                break
            }
            if (editor) {
              editor.redrawGraphic()
            }
          })
          this.initGeometryType()
          this.initGraphic(Point, Polyline, Polygon, Graphic)
        })
    },
    // 校验要编辑的几何类型
    initGeometryType() {
      // 如果有geometry，取geometry的type
      if (this.geometryJson) {
        if (this.geometryJson.paths) {
          this.geometryType = 'polyline'
        } else if (this.geometryJson.rings) {
          this.geometryType = 'polygon'
        } else if (this.geometryJson.x && this.geometryJson.y) {
          this.geometryType = 'point'
        }
      }
      if (!(this.geometryType === 'point') && !(this.geometryType === 'polyline') && !(this.geometryType === 'polygon')) {
        console.error('系统不支持的 geometry Type 类型')
      }
    },
    initGraphic(Point, Polyline, Polygon, Graphic) {
      if (this.geometryJson) {
        if (this.geometryType === 'point') {
          this.geometry = new Point({ x: this.geometryJson.x,
            y: this.geometryJson.y,
            spatialReference: { wkid: 102100 }})
          this.graphicsLyr.graphics.add(new Graphic({ geometry: this.geometry, symbol: this.markSymbol }))
          this.view.center = this.geometry
          this.view.zoom = 14
        } else if (this.geometryType === 'polyline') {
          this.geometry = new Polyline({ paths: this.geometryJson.paths,
            spatialReference: { wkid: 102100 }
          })
          this.graphicsLyr.graphics.add(new Graphic({ geometry: this.geometry, symbol: this.lineSymbol }))
        } else if (this.geometryType === 'polygon') {
          this.geometry = new Polygon({ rings: this.geometryJson.rings,
            spatialReference: { wkid: 102100 }
          })
          this.graphicsLyr.graphics.add(new Graphic({ geometry: this.geometry, symbol: this.fillSymbol }))
        } else {
          console.log('系统不支持的 Geometry 类型')
          return
        }
        this.view.goTo(this.geometry)
      }
    },
    updateData(evt) {
      // 更新graphic显示，并将结果返回
      let newGeometryPro = null; let geometryJson = null; let geojson = null
      if (this.geometryType === 'point') {
        const pointEditor = this.$refs.point
        this.pointDialog.visible = false
        if (pointEditor.graphic) {
          this.graphicsLyr.graphics.removeAll()
          this.graphicsLyr.graphics.add(pointEditor.graphic)
          this.geometry = pointEditor.graphic.geometry
        }
      } else if (this.geometryType === 'polyline') {
        this.polylineDialog.visible = false
        const lineEditor = this.$refs.polyline
        if (lineEditor.graphic) {
          this.graphicsLyr.graphics.removeAll()
          this.graphicsLyr.graphics.add(lineEditor.graphic)
          this.geometry = lineEditor.graphic.geometry
        }
      } else if (this.geometryType === 'polygon') {
        this.polygonDialog.visible = false
        const polygonEditor = this.$refs.polygon
        if (polygonEditor.graphic) {
          this.graphicsLyr.graphics.removeAll()
          this.graphicsLyr.graphics.add(polygonEditor.graphic)
          this.geometry = polygonEditor.graphic.geometry
        }
      }
      if (this.geometry) {
        geometryJson = geometryToJson(this.geometry)
        newGeometryPro = this.webMercatorUtils.webMercatorToGeographic(this.geometry)
        geojson = geometryToGeojson(newGeometryPro)
        this.$emit('geometrycallback', {
          geometry: geometryJson,
          geojson: geojson
        })
      }
      this.view.goTo(this.geometry)
    }
  }
}
</script>
<style scoped="scoped">
    #viewDiv {
        padding: 0;
        margin: 0;
        height: 100%;
        width: 100%;
    }
</style>
<style lang="scss">
.editor-dialog{
  .el-dialog__body{
    max-height: initial ;
    height: calc(100vh - 100px);
  }
}
.geometry-editor-maptip{
  z-index: 9999;
  color: red;
  position:relative;
  top:5px;
  left: 5px;
}
</style>
